// CS U213 Spring 2009
// Assignment 3
// Problem 3.1
// October 2, 2008

/*   
            +-------------------------+
            |   +----------------+    |
            |   |                |    |
            v   v                |    |
         +---------+             |    |
         | ILoP    |             |    |
         +---------+             |    |
             / \                 |    |
             ---                 |    |
              |                  |    |
      ---------------------      |    |
      |                   |      |    |
  +-------+   +---------------+  |    |
  | MtLoP |   | ConsLoP       |  |    |
  +-------+   +---------------+  |    |
            +-| IPlayer first |  |    |
            | | ILoP rest     |--+    |
            | +---------------+       |
            v                         |
       +---------+                    |
       | IPlayer |                    |
       +---------+                    |
           / \                        |
           ---                        |
            |                         |
       ----------------------         |
       |                    |         |
  +-------------+   +--------------+  |
  | Member      |   | Captain      |  |
  +-------------+   +--------------+  |
  | String name |   | String name  |  |
  | int age     |   | int age      |  |
  +-------------+   | String team  |  |
                    | ILoP players |--+
                    +--------------+
*/

// to represent a list of players
interface ILoP {

}

// to represent an empty list of players
class MtLoP implements ILoP {
  MtLoP() {}

}

// to represent a list of players
class ConsLoP implements ILoP {
  IPlayer first; 
  ILoP rest;
  
  ConsLoP(IPlayer first, ILoP rest){
    this.first = first; 
    this.rest = rest; 
  } 

/* TEMPLATE:
   FIELDS:
    ... this.first ...             -- IPlayer
    ... this.rest ...              -- ILoP

    METHODS:
    ... this.mmm() ...            -- ???

    METHODS FOR FIELDS:
    ... this.first.nnn() ...             -- ??
    ... this.rest.mmm() ...              -- ???
*/
}

// to represent a player or a captain on a soccer team
interface IPlayer{}

// to represent a player on a soccer team
class Member implements IPlayer{
  String name;
  int age;
  
  Member(String name, int age){
    this.name = name;
    this.age = age;
  }
}

// to represent a captain on a soccer team
class Captain implements IPlayer{
  String name;
  int age;
  String team;
  ILoP players;
  
  Captain(String name, int age, String team, ILoP players){
    this.name = name;
    this.age = age;
    this.team = team;
    this.players = players;
  } 
}

// examples of soccer leagues data and tests for the methods
class Examples{
  Examples(){}
  
  ILoP mtlop = new MtLoP();
  
  // players -- team members of the team Real
  IPlayer tony = new Member("Tony", 19);
  IPlayer joey = new Member("Joey", 21);
  IPlayer pete = new Member("Pete", 18);
  IPlayer jake = new Member("Jake", 18);
  
  // list of player on the team Real
  ILoP realTeam = new ConsLoP(this.tony, 
                   new ConsLoP(this.joey, 
                    new ConsLoP(this.pete, 
                     new ConsLoP(this.jake, this.mtlop))));

  // players -- team members of the team Sting
  IPlayer jenny = new Member("Jenny", 19);
  IPlayer chris = new Member("Chris", 20);
  IPlayer kerry = new Member("Kerry", 22);
  IPlayer sasha = new Member("Sasha", 17);

  // list of player on the team Sting
  ILoP stingTeam = new ConsLoP(this.jenny, 
                    new ConsLoP(this.chris, 
                     new ConsLoP(this.kerry, 
                      new ConsLoP(this.sasha, this.mtlop))));
                     
  // players -- team members of the team Rex
  IPlayer kim = new Member("Kim", 19);
  IPlayer jan = new Member("Jan", 18);
  IPlayer cas = new Member("Cas", 21);
  IPlayer tim = new Member("Tim", 17);

  // list of player on the team Rex
  ILoP rexTeam = new ConsLoP(this.kim, 
                  new ConsLoP(this.jan, 
                   new ConsLoP(this.cas, 
                    new ConsLoP(this.tim, this.mtlop))));
  // captains
  IPlayer alex  = new Captain("Alex",  20, "Real",  this.realTeam);
  IPlayer ramon = new Captain("Ramon", 20, "Sting", this.stingTeam);
  IPlayer pat   = new Captain("Pat",   20, "Rex",   this.rexTeam);
  
  ILoP league = new ConsLoP(this.alex, 
                 new ConsLoP(this.ramon, 
                  new ConsLoP(this.pat, this.mtlop)));

}